package com.tanhua.admin.service;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.tanhua.admin.exception.BusinessException;
import com.tanhua.admin.interceptor.AdminHolder;
import com.tanhua.admin.mapper.AdminMapper;
import com.tanhua.commons.constant.Constants;
import com.tanhua.commons.utils.JwtUtils;
import com.tanhua.model.db.Admin;
import com.tanhua.model.vo.AdminVo;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;

import java.time.Duration;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.TimeUnit;

@Service
@Slf4j
public class AdminService extends ServiceImpl<AdminMapper, Admin> {

    @Autowired
    private AdminMapper adminMapper;

    @Autowired
    private StringRedisTemplate stringRedisTemplate;
    /**
     * 保存生成的验证码
     * @param uuid
     * @param code
     */
    public void saveCode(String uuid, String code) {
        String key = Constants.CAP_CODE + uuid;
        // 缓存验证码，10分钟后失效
        stringRedisTemplate.opsForValue().set(key,code, Duration.ofMinutes(10));
    }

    /**
     * 用户登录
     * @param paramMap
     * @return
     */
    public Map<String, String> login(Map<String, String> paramMap) {
        //取出用户名与密码, 如果其中有一个为空，报错
        String username = paramMap.get("username");
        String password = paramMap.get("password");
        if(StringUtils.isEmpty(username) || StringUtils.isEmpty(password)){
            throw new BusinessException("用户名或密码不能为空!");
        }
        //1. 校验前端与redis中的验证码
        String verificationCode = paramMap.get("verificationCode");
        if(StringUtils.isEmpty(verificationCode)){
            throw new BusinessException("验证码不能为空!");
        }
        // 取redis中的验证码
        String uuid = paramMap.get("uuid");
        String key = Constants.CAP_CODE + uuid;
        String codeInRedis = stringRedisTemplate.opsForValue().get(key);
        log.info("verificationCode={}, codeInRedis={}", verificationCode, codeInRedis);
        if (!StringUtils.equals(verificationCode,codeInRedis)) {
            throw new BusinessException("验证码不正确!");
        }
        // 移除redis中的验证
        stringRedisTemplate.delete(key);
        //2. 判断用户名与密码是否正确
        // 数据库的密码是加密的，加密才来查
        password = DigestUtils.md5Hex(password);
        Admin admin = query().eq("username", username).eq("password", password).one();
        if(null == admin){
            throw new BusinessException("用户名或密码错误!");
        }
        //3. 如果正确，签发token
        String token = JwtUtils.createToken(admin.getId(), admin.getUsername());
        // 存入redis
        String adminJsonString = JSON.toJSONString(admin);
        String tokenKey = "TOKEN_" + token;
        stringRedisTemplate.opsForValue().set(tokenKey, adminJsonString, 30, TimeUnit.MINUTES);
        //4. 构建返回数据
        Map<String,String> resultMap = new HashMap<>();
        resultMap.put("token", token);
        return resultMap;
    }

    /**
     * 获取登录用户信息
     * @return
     */
    public AdminVo getProfile() {
        Admin loginUser = AdminHolder.getAdmin();
        AdminVo vo = AdminVo.init(loginUser);
        return vo;
    }
}
